package com.ibeeking.found.msg.rest.service.impl;

import com.ibeeking.found.msg.rest.service.IWxMpFansService;
import com.ibeeking.found.msg.rest.service.IWxMpFansTagsService;
import com.ibeeking.found.msg.service.common.bo.WxMpFansTagsBO;
import com.ibeeking.found.msg.service.common.dos.WxMpFansDO;
import com.ibeeking.found.msg.service.common.dos.WxMpFansTagsDO;
import com.ibeeking.found.msg.service.common.param.WxMpTagsFansBatchParam;
import com.ibeeking.found.msg.service.common.param.WxMpTagsFansCancelParam;
import com.ibeeking.found.msg.service.mapper.WxMpFansTagsMapper;
import com.ibeeking.nematos.utils.data.Collections3;
import com.ibeeking.nematos.utils.data.DataUtils;
import com.ibeeking.nematos.utils.json.JsonUtils;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;

/**
 * @Author ibeeking
 */
@Service
public class WxMpFansTagsServiceImpl extends ServiceImpl<WxMpFansTagsMapper, WxMpFansTagsDO> implements IWxMpFansTagsService {

    @Resource
    private WxMpFansTagsMapper wxMpFansTagsMapper;

    @Lazy
    @Resource
    private IWxMpFansService mpFansServiceImpl;

    @Transactional(rollbackFor = Exception.class)
    @Override
    public Boolean removeFansTagsByTagsId(WxMpTagsFansCancelParam param) {
        List<Long> fanIds;
        if (null != param.getFansIds() && param.getFansIds().length > 0) {
            fanIds = Arrays.asList(param.getFansIds());
        } else {
            //查询符合条件的所有粉丝ID
            fanIds = mpFansServiceImpl.queryFansList(param.getQuery());
        }
        if (Collections3.isEmpty(fanIds)) {
            return false;
        }

        List<List<Long>> groupList = DataUtils.groupList(fanIds, 2000);
        groupList.stream().forEach(l -> wxMpFansTagsMapper.deleteByTagsIdAndFansIds(param.getQuery().getAppId(), param.getTagsId(), l));
        return true;
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public Boolean taggingFans(WxMpTagsFansBatchParam param) {
        List<Long> fanIds;
        if (null != param.getFansIds() && param.getFansIds().length > 0) {
            fanIds = Arrays.asList(param.getFansIds());
        } else {
            //查询符合条件的所有粉丝ID
            fanIds = mpFansServiceImpl.queryFansList(param.getQuery());
        }
        if (Collections3.isEmpty(fanIds)) {
            return false;
        }
        List<WxMpFansTagsDO> add = new ArrayList<>();
        List<Long> tagsIds = Arrays.asList(param.getTagsIds());
        for (int i = 0; i < fanIds.size(); i++) {
            for (int j = 0; j < tagsIds.size(); j++) {
                WxMpFansTagsDO wxMpFansTagsDO = new WxMpFansTagsDO();
                wxMpFansTagsDO.setFansId(fanIds.get(i));
                wxMpFansTagsDO.setTagsId(tagsIds.get(j));
                wxMpFansTagsDO.setAppId(param.getQuery().getAppId());
                wxMpFansTagsDO.setDelStatus(0);
                add.add(wxMpFansTagsDO);
            }
        }

        List<WxMpFansTagsDO> wxMpFansTagsDOS = wxMpFansTagsMapper.selectList(new LambdaQueryWrapper<>(WxMpFansTagsDO.class)
                .eq(WxMpFansTagsDO::getAppId, param.getQuery().getAppId())
                .in(WxMpFansTagsDO::getTagsId, tagsIds)
        );

        if (!Collections3.isEmpty(wxMpFansTagsDOS)) {
            //重置标签
            List<Long> ids = wxMpFansTagsDOS.parallelStream().filter(wxMpFansTagsDO -> fanIds.contains(wxMpFansTagsDO.getFansId())).map(WxMpFansTagsDO::getId).collect(Collectors.toList());
            if (!Collections3.isEmpty(ids)) {
                wxMpFansTagsMapper.deleteIds(ids);
            }
        }
        List<List<WxMpFansTagsDO>> groups = DataUtils.groupList(add, 2000);
        //新增标签
        groups.stream().forEach(l -> wxMpFansTagsMapper.insertBatchSomeColumn(l));
        return true;
    }

    @Override
    public List<Long> queryFansIdsByTagsId(String appId, Long tagsId) {
        List<WxMpFansTagsDO> wxMpFansTagsDOS = wxMpFansTagsMapper.selectList(new LambdaQueryWrapper<>(WxMpFansTagsDO.class).eq(WxMpFansTagsDO::getAppId, appId).eq(WxMpFansTagsDO::getTagsId, tagsId));
        if (Collections3.isEmpty(wxMpFansTagsDOS)) {
            return Collections3.emptyList();
        }
        return wxMpFansTagsDOS.parallelStream().map(WxMpFansTagsDO::getFansId).collect(Collectors.toList());
    }

    @Override
    public List<WxMpFansTagsBO> queryTagsIdsByFansIds(String appId, List<Long> fansIds) {
        List<WxMpFansTagsDO> wxMpFansTagsDOS = wxMpFansTagsMapper.selectList(new LambdaQueryWrapper<>(WxMpFansTagsDO.class).eq(WxMpFansTagsDO::getAppId, appId).in(WxMpFansTagsDO::getFansId, fansIds));
        if (Collections3.isEmpty(wxMpFansTagsDOS)) {
            return Collections3.emptyList();
        }
        return JsonUtils.jsonToList(wxMpFansTagsDOS, WxMpFansTagsBO.class);
    }

    @Override
    public List<String> queryByFansId(Long fansId) {
        List<WxMpFansTagsDO> wxMpFansTagsDOS = wxMpFansTagsMapper.selectList(new LambdaQueryWrapper<>(WxMpFansTagsDO.class).eq(WxMpFansTagsDO::getFansId, fansId));
        if (Collections3.isEmpty(wxMpFansTagsDOS)) {
            return Collections3.emptyList();
        }
        return wxMpFansTagsDOS.stream().map(wxMpFansTagsDO -> String.valueOf(wxMpFansTagsDO.getTagsId())).collect(Collectors.toList());
    }

    @Override
    public Boolean modifyTags(String appId, Long fansId, List<Long> tagsList) {
        wxMpFansTagsMapper.deleteByFansId(fansId);
        if (!Collections3.isEmpty(tagsList)) {
            List<WxMpFansTagsDO> saves = new ArrayList<>();
            tagsList.stream().forEach(tagsId -> {
                WxMpFansTagsDO wxMpFansTagsDO = new WxMpFansTagsDO();
                wxMpFansTagsDO.setFansId(fansId);
                wxMpFansTagsDO.setTagsId(tagsId);
                wxMpFansTagsDO.setAppId(appId);

                saves.add(wxMpFansTagsDO);
            });
            wxMpFansTagsMapper.insertBatchSomeColumn(saves);
        }
        return true;
    }

    /**
     * 使用多标签查询粉丝信息
     *
     * @param tagIds
     * @param appId
     * @return
     */
    @Override
    public List<WxMpFansDO> queryFansByTagsIds(List<Long> tagIds, String appId) {
        return this.wxMpFansTagsMapper.queryFansByTagsIds(tagIds, appId);
    }
}
